"""
信息融合处理器
负责融合视觉分析结果和样本数据
"""
import sys
import os
from typing import Dict, Any, Optional

# 添加项目根目录到Python路径
sys.path.append(os.path.dirname(os.path.dirname(os.path.dirname(os.path.dirname(os.path.abspath(__file__))))))

from src.text.sample_data_loader import get_sample_data_loader, SampleDataLoader


class InformationFusionProcessor:
    """
    信息融合处理器类
    用于融合视觉分析结果和样本数据，提取关键信息
    """
    
    def __init__(self, sample_data_loader: Optional[SampleDataLoader] = None):
        """
        初始化信息融合处理器
        
        Args:
            sample_data_loader: 样本数据加载器实例，如果为None则使用默认实例
        """
        self.sample_data_loader = sample_data_loader or get_sample_data_loader()
    
    def fuse_information(self, vision_result: Dict[str, Any], video_id: str) -> Dict[str, Any]:
        """
        融合视觉分析结果和样本数据
        
        Args:
            vision_result: 视觉分析结果
            video_id: 视频ID
            
        Returns:
            Dict[str, Any]: 融合后的信息
        """
        # 获取样本数据
        sample_data = self._get_sample_data(video_id)
        
        # 提取视觉分析中的关键信息
        vision_info = self._extract_vision_info(vision_result)
        
        # 融合数据
        fused_data = {
            "video_id": video_id,
            "sample_data": sample_data,
            "vision_analysis": vision_info,
            "known_fields": self._get_known_fields(vision_result),
            "fields_to_supplement": self._get_fields_to_supplement(vision_result),
            "context_info": self._build_context_info(sample_data, vision_info)
        }
        
        return fused_data
    
    def _get_sample_data(self, video_id: str) -> Dict[str, Any]:
        """
        获取视频样本数据
        
        Args:
            video_id: 视频ID
            
        Returns:
            Dict[str, Any]: 样本数据，如果未找到则返回空字典
        """
        try:
            sample = self.sample_data_loader.get_sample_by_video_id(video_id)
            return sample if sample else {}
        except Exception as e:
            # 记录错误但不中断流程
            print(f"获取样本数据时出错: {e}")
            return {}
    
    def _extract_vision_info(self, vision_result: Dict[str, Any]) -> Dict[str, Any]:
        """
        从视觉分析结果中提取关键信息
        
        Args:
            vision_result: 视觉分析结果
            
        Returns:
            Dict[str, Any]: 提取的视觉分析信息
        """
        extracted_info = {}
        
        if 'encoding_categories' in vision_result:
            categories = vision_result['encoding_categories']
            
            # 提取每个类别的关键信息
            for category_key, category_info in categories.items():
                if isinstance(category_info, dict):
                    extracted_info[category_key] = {
                        'option': category_info.get('option', ''),
                        'confidence': category_info.get('confidence', 0),
                        'source': category_info.get('source', 'vision_analysis')
                    }
        
        return extracted_info
    
    def _get_known_fields(self, vision_result: Dict[str, Any]) -> Dict[str, Any]:
        """
        获取视觉分析中已有确定结果的字段
        
        Args:
            vision_result: 视觉分析结果
            
        Returns:
            Dict[str, Any]: 已有确定结果的字段及其值
        """
        known_fields = {}
        
        if 'encoding_categories' in vision_result:
            categories = vision_result['encoding_categories']
            
            for category_key, category_info in categories.items():
                if isinstance(category_info, dict):
                    option = category_info.get('option', '')
                    confidence = category_info.get('confidence', 0)
                    
                    # 只保留置信度较高且有确定结果的字段
                    if option and option.lower() != '未知' and confidence >= 70:
                        known_fields[category_key] = option
        
        return known_fields
    
    def _get_fields_to_supplement(self, vision_result: Dict[str, Any]) -> list:
        """
        获取需要补充分析的字段
        
        Args:
            vision_result: 视觉分析结果
            
        Returns:
            list: 需要补充分析的字段列表
        """
        # 如果结果中已经指定了需要补充的字段，则直接使用
        if 'fields_to_supplement' in vision_result:
            return vision_result['fields_to_supplement']
        
        # 否则，根据置信度和结果内容自动判断
        fields_to_supplement = []
        
        if 'encoding_categories' in vision_result:
            categories = vision_result['encoding_categories']
            
            for category_key, category_info in categories.items():
                if isinstance(category_info, dict):
                    option = category_info.get('option', '')
                    confidence = category_info.get('confidence', 0)
                    
                    # 置信度低或结果为未知的字段需要补充
                    if confidence < 70 or option.lower() == '未知':
                        fields_to_supplement.append(category_key)
        
        return fields_to_supplement
    
    def _build_context_info(self, sample_data: Dict[str, Any], vision_info: Dict[str, Any]) -> Dict[str, Any]:
        """
        构建上下文信息，用于提示词生成
        
        Args:
            sample_data: 样本数据
            vision_info: 视觉分析信息
            
        Returns:
            Dict[str, Any]: 上下文信息
        """
        context = {
            "video_title": sample_data.get('视频标题', '').strip(),
            "video_description": sample_data.get('视频描述', '').strip(),
            "author_name": sample_data.get('作者昵称', '').strip(),
            "publish_time": sample_data.get('发布时间', '').strip(),
        }
        
        # 添加视觉分析中置信度较高的结果到上下文
        for key, info in vision_info.items():
            if info.get('confidence', 0) >= 70 and info.get('option', '').lower() != '未知':
                context[key] = info.get('option', '')
        
        # 移除空值
        context = {k: v for k, v in context.items() if v}
        
        return context
    
    def format_known_info(self, known_fields: Dict[str, Any], field_name: str) -> str:
        """
        格式化已知信息，用于提示词中的已知信息部分
        排除当前正在分析的字段，避免循环引用
        
        Args:
            known_fields: 已知字段字典
            field_name: 当前正在分析的字段名
            
        Returns:
            str: 格式化后的已知信息
        """
        # 排除当前正在分析的字段
        filtered_fields = {k: v for k, v in known_fields.items() if k != field_name}
        
        if not filtered_fields:
            return "暂无其他已知信息"
        
        # 构建字段名映射，使其更友好
        field_name_mapping = {
            "scene_setting": "场景设定",
            "theme_type": "主题类型",
            "emotional_tendency": "情感倾向",
            "content_category": "内容类别",
            "age_group": "适合年龄",
            "gender_orientation": "性别倾向",
            "interaction_type": "互动类型"
        }
        
        # 格式化已知信息
        info_parts = []
        for field_key, field_value in filtered_fields.items():
            friendly_name = field_name_mapping.get(field_key, field_key)
            info_parts.append(f"{friendly_name}: {field_value}")
        
        return "；".join(info_parts)


# 创建全局信息融合处理器实例，用于单例访问
_fusion_processor_instance: Optional[InformationFusionProcessor] = None


def get_information_fusion_processor() -> InformationFusionProcessor:
    """
    获取信息融合处理器的单例实例
    
    Returns:
        InformationFusionProcessor: 信息融合处理器实例
    """
    global _fusion_processor_instance
    if _fusion_processor_instance is None:
        _fusion_processor_instance = InformationFusionProcessor()
    return _fusion_processor_instance


# 测试代码
if __name__ == "__main__":
    try:
        # 创建测试数据
        test_vision_result = {
            "status": "success",
            "video_id": "video_001",
            "encoding_categories": {
                "scene_setting": {
                    "name": "场景设定",
                    "option": "校园场景",
                    "confidence": 90,
                    "source": "vision_analysis"
                },
                "theme_type": {
                    "name": "主题类型",
                    "option": "未知",
                    "confidence": 40,
                    "source": "vision_analysis"
                },
                "emotional_tendency": {
                    "name": "情感倾向",
                    "option": "",
                    "confidence": 30,
                    "source": "vision_analysis"
                }
            },
            "fields_to_supplement": ["theme_type", "emotional_tendency"]
        }
        
        test_video_id = "video_001"
        
        # 创建融合处理器实例
        fusion_processor = InformationFusionProcessor()
        
        # 测试融合信息
        print("开始融合信息...")
        fused_data = fusion_processor.fuse_information(test_vision_result, test_video_id)
        
        # 打印融合结果
        print("\n融合结果:")
        print(f"视频ID: {fused_data['video_id']}")
        print(f"已知字段: {fused_data['known_fields']}")
        print(f"需要补充的字段: {fused_data['fields_to_supplement']}")
        print(f"上下文信息: {fused_data['context_info']}")
        
        # 测试格式化已知信息
        known_info = fusion_processor.format_known_info(fused_data['known_fields'], "theme_type")
        print(f"\n格式化后的已知信息: {known_info}")
        
    except Exception as e:
        print(f"测试出错: {e}")